/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */

package logica;

import fisica.CapaFisica;
import fisica.PersonaFisica;
import hibernate.objeto.Persona;
import hibernate.objeto.Usuario;
import java.util.Date;
import java.util.Vector;
import javax.swing.JOptionPane;
import presentacion.CapaPresentacion;
import presentacion.MenuPrincipal;
import presentacion.utilidad.MensajePresentacion;

/**
 *
 * @author Gonzalo
 */
public class PersonaLogica extends CapaLogica {

    /**
     * Agrega o modifica un objeto persona persisitiendola en la base de datos.
     *
     * @param datosPersona Los datos de la persona recopilados en la capa
     * superior.
     * @param persona El objeto persona que se esta agregando/modificando
     * @param idPersona Un arreglo en donde se guarda el id del objeto
     * Persona creado para su posterior recuperación
     * @return true si se agregó/modificó correctamente, false en caso contrario
     */
    public static boolean agregarOModificarPersona(Object[] datosPersona,
            Persona persona, int[] idPersona){
        //Crea el objeto
        persona = crearUObtenerObjetoPersona(datosPersona, persona);

        //Persiste el objeto
        if (CapaFisica.guardarOActualizarObjeto(persona)) {
            //Almacena el id del objeto creado
            idPersona[0] = persona.getIdPersona();
            return true;
        } else {
            return false;
        }
    }

    /**
     * Crea o modifica un objeto persona según los datos pasados por parámetro.
     *
     * @param datosPersona Los datos de la persona recopilados en la capa
     * superior.
     * @param persona El objeto persona que se esta agregando/modificando
     * @return El objeto Persona creado
     */
    private static Persona crearUObtenerObjetoPersona(Object[] datosPersona,
            Persona persona) {
        //Verifica que la persona exista en la bd físicamente pero no esté activa
        Persona personaExistio = PersonaFisica.getPersonaPorDocumentoYEnBd(
                datosPersona[CapaLogica.PERSONA_TIPO_DE_DOCUMENTO].toString(),
                datosPersona[CapaLogica.PERSONA_NUMERO_DE_DOCUMENTO].toString(),
                false);

        //Si la persona existe, se la reactiva
        if (personaExistio != null) {
            personaExistio.setEnBdPersona(true);
            persona = personaExistio;
        }

        //Si se trata de una nueva persona
        if (persona == null) {
            //Se crea el nuevo objeto
	    persona = new Persona();
        }

        //Se continúa seteando los distintos datos
        //Seteo del tipo de documento
        persona.setTipoDeDocumentoPersona(
                datosPersona[CapaLogica.PERSONA_TIPO_DE_DOCUMENTO].toString());

        //Seteo del número de documento
        persona.setNumeroDeDocumentoPersona(
                datosPersona[CapaLogica.PERSONA_NUMERO_DE_DOCUMENTO].toString());

        //Seteo del nombre.
        //El mismo se almacena capitalizado solo en la primer letra de cada nombre
        persona.setNombrePersona(eliminarEspaciosMuertos(capitalizeFirstLetter(
                datosPersona[CapaLogica.PERSONA_NOMBRE].toString())));

        //Seteo del apellido.
        //El mismo se almacena capitalizado solo en la primer letra de cada apellido
        persona.setApellidoPersona(eliminarEspaciosMuertos(capitalizeFirstLetter(
                datosPersona[CapaLogica.PERSONA_APELLIDO].toString())));

        //Seteo de la fecha, en caso de que corresponda
        if (datosPersona[CapaLogica.PERSONA_FECHA_DE_NACIMIENTO] != null) {
            persona.setFechaDeNacimientoPersona(
                    (Date) datosPersona[CapaLogica.PERSONA_FECHA_DE_NACIMIENTO]);
        }

        //Seteo del teléfono particular
        persona.setTelefonoParticularPersona(
                datosPersona[CapaLogica.PERSONA_TELEFONO_PARTICULAR].
                toString());

        //Seteo del teléfono móvil
        persona.setTelefonoMovilPersona(
                datosPersona[CapaLogica.PERSONA_TELEFONO_MOVIL].
                toString());

        //Seteo del correo electrónico
        persona.setCorreoElectronicoPersona(eliminarEspaciosMuertos(
                datosPersona[PERSONA_CORREO_ELECTRONICO].toString()));

        //Seteo del estado lógico
        persona.setEnBdPersona(true);

        //Se retorna el objeto Persona creado
        return persona;
    }

    /**
     * Elimina logicamente la persona.
     *
     * @param persona El objeto Persona a eliminar
     * @return true si se eliminó correctamente, false en caso contrario
     */
    public static boolean eliminarPersona(Persona persona) {
        Usuario usuario = UsuarioLogica.getUsuarioPorDocumentoEnBd(
                persona.getTipoDeDocumentoPersona(),
                persona.getNumeroDeDocumentoPersona());

        if (usuario != null && usuario != MenuPrincipal.usuarioActivo) {
            int confirmaEliminacion =
                    MensajePresentacion.confirmarEliminacionPersonaConUsuario();
            if (confirmaEliminacion == JOptionPane.OK_OPTION) {
                UsuarioLogica.eliminarUsuario(usuario);
                //Setea no activa
                persona.setEnBdPersona(false);
                return CapaFisica.guardarOActualizarObjeto(persona);
            } else {
                return false;
            }
        }
        
        //Setea no activa
        persona.setEnBdPersona(false);
        //Guarda en la base de datos
        return CapaFisica.guardarOActualizarObjeto(persona);
    }

    /**
     * Retorna el objeto Persona según el id.
     *
     * @param id El id de la persona
     * @return El objeto Persona consultado, null si no existe
     */
    public static Persona getPersonaPorIdYEnBd(int id){
        return PersonaFisica.getPersonaPorIdYPorEnBd(id, true);
    }

    /**
     * Retorna un objeto persona según el tipo y número de documento.
     *
     * @param documento El tipo y número de documento consultado
     * @return El objeto Persona requerido
     */
    public static Persona getPersonaPorDocumentoEnBd(String documento) {
        //Se pide a la capa inferior que gestione la consulta
        return PersonaFisica.getPersonaPorDocumentoYEnBd(
                separarTipoDeDocumento(documento),
                separarNumeroDeDocumento(documento), true);
    }

    /**
     * Verifica si existe una persona en la base de datos.
     *
     * @param tipo El tipo de documento
     * @param numero El número de documento
     * @return true si existe, false en caso contrario
     */
    public static boolean existePersonaPorDocumentoEnBd(String tipo, String numero){
        return (PersonaFisica.getPersonaPorDocumentoYEnBd(
                tipo, numero, true) != null);
    }

    /**
     * Verifica si existe una persona por correo electrónico en la base de datos.
     *
     * @param correoElectronico El correo electrónico
     * @return El objeto Usuario consultado, null si no existe
     */
    public static boolean existePersonaPorCorreoElectronicoEnBd(
            String correoElectronico) {
        return (PersonaFisica.getPersonaPorCorreoElectronicoYPorEnBd(
                correoElectronico, true) != null);
    }

    /**
     * Retorna el vector con los objetos Persona según el estado en la base
     * de datos.
     *
     * @param estado 0 si es baja lógica, 1 si aún activo
     * @return El vector de objetos Persona consultado
     */
    public static Vector<Persona> getVectorPersonaYEnBd() {
        return PersonaFisica.getVectorPersonaPorEnBd(1);
    }

    /**
     * Retorna el vector de objetos Persona que sean mayores de edad en la
     * base de datos.
     *
     * @return Un vector con todos los objetos Persona
     */
    public static Vector<Persona> getVectorPersonaMayorDeEdadYEnBd() {
        Vector<Persona> all = getVectorPersonaYEnBd();

        Vector<Persona> retorno = new Vector<Persona>();

        if (all != null) {
            for (int i = 0; i < all.size(); i++) {
                if (!esMenor(all.get(i).getFechaDeNacimientoPersona())) {
                    retorno.add(all.elementAt(i));                    
                }
            }
        }

        return retorno;
    }

    /**
     * Dado el vector de personas que recibe por parametro, retorna uno
     * conteniendo solamente las personas que son pacientes.
     *
     * @param vectorPersona El vector con los objetos Persona
     * @return Un vector con los objetos personas que sí son Pacientes
     */
    public static Vector<Persona> filtrarPorPaciente(
            Vector<Persona> vectorPersona) {

        Vector<Persona> vectorPaciente = new Vector<Persona>();
        Persona unaPersonaDelVector = new Persona();

        //Si no esta vacio
        if (!vectorPersona.isEmpty()) {
            for (int i = 0; i < vectorPersona.size(); i++) {
                unaPersonaDelVector = vectorPersona.get(i);
                if (PacienteLogica.esPaciente(unaPersonaDelVector)) {
                    vectorPaciente.add(vectorPersona.get(i));
                }
            }
        }

        return vectorPaciente;
    }

    /**
     * Dado el vector de personas que recibe por parametro, retorna uno
     * conteniendo solamente las personas que no son pacientes.
     *
     * @param vectorPersona El vector con los objetos Persona
     * @return Un vector con los objetos personas que no son Pacientes
     */
    public static Vector<Persona> filtrarPorContacto(
            Vector<Persona> vectorPersona) {

        Vector<Persona> vectorContacto = new Vector<Persona>();
        Persona unaPersonaDelVector = new Persona();

        //Si no esta vacio
        if (!vectorPersona.isEmpty()) {
            for (int i = 0; i < vectorPersona.size(); i++) {
                unaPersonaDelVector = vectorPersona.get(i);
                if (!PacienteLogica.esPaciente(unaPersonaDelVector)) {
                    vectorContacto.add(vectorPersona.get(i));
                }
            }
        }

        return vectorContacto;
    }

    /**
     * Retorna el texto HTML correspondiente a la descripcion del persona.
     *
     * @param persona La persona
     * @return El String que contiene el HTML
     */
    public static String getPersonaHTML(Persona persona) {
        String personaHTML = "";
        if (persona != null) {
            personaHTML = 
                    "<font size=\"3\" face=\"arial\" color=\"black\">Documento: </font>"
                    + "<font size=\"3\" face=\"arial\">" +
                    CapaPresentacion.imprimirDocumento(persona) + "</font><br>" +
                    "<font size=\"3\" face=\"arial\" color=\"black\">Apellido y Nombre: </font>"
                    + "<font size=\"3\" face=\"arial\">" +
                    CapaPresentacion.imprimirApellidoYNombrePersona(persona) + "</font><br>" +
                    "<font size=\"3\" face=\"arial\" color=\"black\">Fecha de nacimiento: </font>"
                    + "<font size=\"3\" face=\"arial\">" +
                    CapaPresentacion.imprimirFecha(persona.getFechaDeNacimientoPersona()) + "</font><br>" +
                    "<font size=\"3\" face=\"arial\" color=\"black\">Teléfono particular: </font>"
                    + "<font size=\"3\" face=\"arial\">" +
                    persona.getTelefonoParticularPersona() + "</font><br>" +
                    "<font size=\"3\" face=\"arial\" color=\"black\">Teléfono móvil: </font>"
                    + "<font size=\"3\" face=\"arial\">" +
                    persona.getTelefonoMovilPersona() + "</font><br>" +
                    "<font size=\"3\" face=\"arial\" color=\"black\">Correo electrónico: </font>"
                    + "<font size=\"3\" face=\"arial\">" +
                    persona.getCorreoElectronicoPersona() + "</font><br>";
                    
        }
        return personaHTML;
    }
    
}
